//*******************************************************************************
// COPYRIGHT NOTES
// ---------------
// This is a sample for BCGControlBar Library Professional Edition
// Copyright (C) 1998-2016 BCGSoft Ltd.
// All rights reserved.
//
// This source code can be used, distributed or modified
// only under terms and conditions 
// of the accompanying license agreement.
//*******************************************************************************
//
// ChartErrorBarsView.cpp : implementation file
//

#include "stdafx.h"
#include "bcgpchartexample.h"
#include "ChartErrorBarsView.h"

#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif

/////////////////////////////////////////////////////////////////////////////
// CChartErrorBarsView

IMPLEMENT_DYNCREATE(CChartErrorBarsView, CBCGPChartExampleView)

CChartErrorBarsView::CChartErrorBarsView()
	: CBCGPChartExampleView(CChartErrorBarsView::IDD)
{
	//{{AFX_DATA_INIT(CChartErrorBarsView)
	m_nChartCategory = 0;
	m_nChartType = 0;
	m_nErrorBarsType = 5;
	//}}AFX_DATA_INIT
}

CChartErrorBarsView::~CChartErrorBarsView()
{
}

void CChartErrorBarsView::DoDataExchange(CDataExchange* pDX)
{
	CBCGPChartExampleView::DoDataExchange(pDX);
	//{{AFX_DATA_MAP(CChartErrorBarsView)
	DDX_CBIndex(pDX, IDC_CHART_CATEGORY, m_nChartCategory);
	DDX_CBIndex(pDX, IDC_CHART_TYPE, m_nChartType);
	DDX_CBIndex(pDX, IDC_ERRORBARS_TYPE, m_nErrorBarsType);
	DDX_Control(pDX, IDC_CHART_TYPE, m_wndChartType);
	DDX_Control(pDX, IDC_CHART, m_wndChart);
	//}}AFX_DATA_MAP
}


BEGIN_MESSAGE_MAP(CChartErrorBarsView, CBCGPChartExampleView)
	//{{AFX_MSG_MAP(CChartErrorBarsView)
	ON_CBN_SELENDOK(IDC_CHART_CATEGORY, OnUpdateChart)
	ON_CBN_SELENDOK(IDC_CHART_TYPE, OnUpdateChart)
	ON_CBN_SELENDOK(IDC_ERRORBARS_TYPE, OnUpdateChart)
	//}}AFX_MSG_MAP
END_MESSAGE_MAP()

/////////////////////////////////////////////////////////////////////////////
// CChartErrorBarsView diagnostics

#ifdef _DEBUG
void CChartErrorBarsView::AssertValid() const
{
	CBCGPChartExampleView::AssertValid();
}

void CChartErrorBarsView::Dump(CDumpContext& dc) const
{
	CBCGPChartExampleView::Dump(dc);
}
#endif //_DEBUG

/////////////////////////////////////////////////////////////////////////////
// CChartErrorBarsView message handlers

void CChartErrorBarsView::OnInitialUpdate() 
{
	CBCGPChartExampleView::OnInitialUpdate();
	
	if (m_bIsReady)
	{
		return;
	}

	m_bIsReady = TRUE;

	CBCGPChartVisualObject* pChart = m_wndChart.GetChart();
	ASSERT_VALID(pChart);

	pChart->SetThemeOpacity(25);

	OnUpdateChart();
}

BOOL CALLBACK ErrorBarsCallback(int /*nDataPointIndex*/, CBCGPChartSeries* /*pFormulaSeries*/, LPARAM /*lp*/, double& /*dValue*/, double& dMinus, double& dPlus)
{
	dMinus = Rand(0, 5);
	dPlus = Rand(0, 5);

	return TRUE;
}

void CChartErrorBarsView::OnUpdateChart() 
{
	int nChartCategory = m_nChartCategory;

	UpdateData();

	CBCGPChartVisualObject* pChart = m_wndChart.GetChart();
	ASSERT_VALID(pChart);

	pChart->EnableRedraw(FALSE);

	BCGPChartCategory category = BCGPChartLine;
	switch(m_nChartCategory)
	{
	case 1:
		category = BCGPChartColumn;
		break;
	case 2:
		category = BCGPChartBar;
		break;
	case 3:
		category = BCGPChartArea;
		break;
	case 4:
	case 5:
		category = BCGPChartPolar;
		break;
	}

	BCGPChartType type = BCGP_CT_SIMPLE;

	if (category != BCGPChartPolar)
	{
		switch(m_nChartType)
		{
		case 1:
			type = BCGP_CT_STACKED;
			break;
		case 2:
			type = BCGP_CT_100STACKED;
			break;
		}
	}

	if ((pChart->GetChartCategory() != BCGPChartPolar && category == BCGPChartPolar) ||
		(pChart->GetChartCategory() == BCGPChartPolar && category != BCGPChartPolar) ||
		(category == BCGPChartPolar && (nChartCategory - m_nChartCategory) != 0))
	{
		pChart->CleanUpChartData();
	}

	pChart->SetChartType(category, type);

	int i = 0;

	if (pChart->GetSeriesCount() == 0)
	{
		const double arValues[] = { 5, 12, 19, 22, 19, 24, 22, 24, 18, 14, 10, 7 };

		CBCGPChartSeries* pSeries1 = pChart->CreateSeries(_T("Series 1"));

		if (category != BCGPChartPolar)
		{
			CBCGPChartSeries* pSeries2 = pChart->CreateSeries(_T("Series 2"));
			CBCGPChartSeries* pSeries3 = pChart->CreateSeries(_T("Series 3"));

			for (i = 0; i < 12; i++)
			{
				int value = (int)arValues[i];
				pSeries1->AddDataPoint(value);
				pSeries2->AddDataPoint((int)(value + Rand(5, 15)));
				pSeries3->AddDataPoint((int)(value + Rand(15, 25)));
			}
		}
		else
		{
			for (i = 0; i < 12; i++)
			{
				if (m_nChartCategory == 5)
				{
					pSeries1->AddDataPoint(arValues[i]);
				}
				else
				{
					pSeries1->AddDataPoint(arValues[i], i * 30.0);
				}
			}
		}
	}

	BCGPCHART_ERRORBARS_CALLBACK pCallback = NULL;
	CBCGPChartErrorBarsFormula::ErrorBarsType errors = CBCGPChartErrorBarsFormula::EBT_STD_S;
	switch(m_nErrorBarsType)
	{
	case 1:
		errors = CBCGPChartErrorBarsFormula::EBT_STD_P;
		break;
	case 2:
		errors = CBCGPChartErrorBarsFormula::EBT_SEM_SE;
		break;
	case 3:
		errors = CBCGPChartErrorBarsFormula::EBT_SEM_SD;
		break;
	case 4:
		errors = CBCGPChartErrorBarsFormula::EBT_FIXED;
		break;
	case 5:
		errors = CBCGPChartErrorBarsFormula::EBT_PERCENT;
		break;
	case 6:
		errors = CBCGPChartErrorBarsFormula::EBT_DIFF;
		break;
	case 7:
		errors = CBCGPChartErrorBarsFormula::EBT_CUSTOM;
		pCallback = &ErrorBarsCallback;
		break;
	}

	CBCGPChartErrorBarsFormula formula(errors, NULL, pCallback);

	for (i = 0; i < pChart->GetSeriesCount(); i++)
	{
		CBCGPChartSeries* pSeries = pChart->GetSeries(i);
		ASSERT_VALID(pSeries);

		BCGPChartFormatSeries style = pSeries->GetSeriesFormat();

		style.m_shadowType.m_bDisplayShadow = TRUE;
		style.SetSeriesLineWidth(category == BCGPChartLine || category == BCGPChartPolar ? theApp.GetDefaultLineWidth() : 1.0);

		pSeries->SetSeriesFormat(style);
		pSeries->CreateErrorBars(formula);
	}

	pChart->EnableRedraw(TRUE);

	pChart->Redraw();
}
